﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Linq.Expressions;
using System.Threading.Tasks;
using XiangziProjectTemplete.Core.AuthHelper.OverWrite;
using XiangziProjectTemplete.Core.Common.Helper;
using XiangziProjectTemplete.Core.Common.HttpContextUser;
using XiangziProjectTemplete.Core.Extensions.Others;
using XiangziProjectTemplete.Core.IRepository.UnitOfWork;
using XiangziProjectTemplete.Core.IServices;
using XiangziProjectTemplete.Core.Model;
using XiangziProjectTemplete.Core.Model.Models;
using XiangziProjectTemplete.Core.Model.ParamModels;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;

namespace XiangziProjectTemplete.Core.Controllers
{
    /// <summary>
    /// 用户管理
    /// </summary>
    [Route("api/[controller]/[action]")]
    [ApiController]
    [Authorize(Permissions.Name)]
    public class UserController : ControllerBase
    {
        private readonly IUnitOfWork _unitOfWork;
        readonly ISysUserInfoServices _sysUserInfoServices;
        readonly IUserRoleServices _userRoleServices;
        readonly IRoleServices _roleServices;
        private readonly IUser _user;
        private readonly ILogger<UserController> _logger;
        private IWebHostEnvironment _environment;//将IWebHostEnvironment注入到Controller中，并分配给私有属性Environment，随后用于获取WebRootPath和ContentRootPath。

        /// <summary>
        /// 构造函数
        /// </summary>
        /// <param name="unitOfWork"></param>
        /// <param name="sysUserInfoServices"></param>
        /// <param name="userRoleServices"></param>
        /// <param name="roleServices"></param>
        /// <param name="user"></param>
        /// <param name="logger"></param>
        ///  <param name="environment"></param>
        public UserController(IUnitOfWork unitOfWork, ISysUserInfoServices sysUserInfoServices,
            IUserRoleServices userRoleServices, IRoleServices roleServices, IUser user, ILogger<UserController> logger
            , IWebHostEnvironment environment)
        {
            _unitOfWork = unitOfWork;
            _sysUserInfoServices = sysUserInfoServices;
            _userRoleServices = userRoleServices;
            _roleServices = roleServices;
            _user = user;
            _logger = logger;
            _environment = environment;
        }

        /// <summary>
        /// 获取全部用户
        /// </summary>
        /// <param name="param"></param>
        /// <returns></returns>
        // GET: api/User
        [HttpPost]
        public async Task<MessageModel<PageModel<sysUserInfo>>> Get([FromBody] UserInfoParam param)
        {
            if (param.searchVal == null)
            {
                param.searchVal = string.Empty;
            }
            var data = await _sysUserInfoServices.Query(a => (a.tdIsDelete != true && a.uStatus >= 0));

            #region MyRegion

            // 这里可以封装到多表查询，此处简单处理
            var allUserRoles = await _userRoleServices.Query(d => d.IsDeleted == false);
            var allRoles = await _roleServices.Query(d => d.IsDeleted == false);

            var sysUserInfos = data;
            foreach (var item in sysUserInfos)
            {
                var currentUserRoles = allUserRoles.Where(d => d.UserId == item.uID).Select(d => d.RoleId).ToList();
                item.RIDs = currentUserRoles;
                item.RoleNames = allRoles.Where(d => currentUserRoles.Contains(d.Id)).Select(d => d.Name).ToList();
            }
            data = sysUserInfos;



            var whereConditions = WhereConditionsExtensions.GetWhereConditions<sysUserInfo, UserInfoParam>(param);
            if (!whereConditions.IsSuccess)
            {
                return new MessageModel<PageModel<sysUserInfo>>()
                {
                    msg = whereConditions.ErrMsg,
                    success = false,
                    response = null
                };
            }

            //手动分页
            int totalPage = 0;
            int dataCount = 0;//总数

            //增加过滤
            Expression<Func<sysUserInfo, bool>> whereExpression2 = a => a.tdIsDelete != true;
            whereConditions.data = whereConditions.data.And(whereExpression2);

            data = ListHelper.ListPage<sysUserInfo>(data, whereConditions.data, param.page, param.pageSize, out totalPage, out dataCount);
            data = data.OrderByDescending(x => x.uID).ToList();

            #endregion

            PageModel<sysUserInfo> resultData = new PageModel<sysUserInfo>()
            {
                page = param.page,
                pageSize = param.pageSize,
                pageCount = totalPage,
                data = data,
                dataCount = dataCount
            };
            return new MessageModel<PageModel<sysUserInfo>>()
            {
                msg = "获取成功",
                success = data.Count >= 0,
                response = resultData
            };

        }

        // GET: api/User/5
        [HttpGet("{id}")]
        [AllowAnonymous]
        public string Get(string id)
        {
            _logger.LogError("test wrong");
            return "value";
        }

        // GET: api/User/5
        /// <summary>
        /// 获取用户详情根据token
        /// 【无权限】
        /// </summary>
        /// <param name="token">令牌</param>
        /// <returns></returns>
        [HttpGet]
        [AllowAnonymous]
        public async Task<MessageModel<sysUserInfo>> GetInfoByToken(string token)
        {
            var data = new MessageModel<sysUserInfo>();
            if (!string.IsNullOrEmpty(token))
            {
                var tokenModel = JwtHelper.SerializeJwt(token);
                if (tokenModel != null && tokenModel.Uid > 0)
                {
                    var userinfo = await _sysUserInfoServices.QueryById(tokenModel.Uid);
                    if (userinfo != null)
                    {
                        data.response = userinfo;
                        data.success = true;
                        data.msg = "获取成功";
                    }
                }

            }
            return data;
        }

        /// <summary>
        /// 添加一个用户
        /// </summary>
        /// <param name="sysUserInfo"></param>
        /// <returns></returns>
        // POST: api/User
        [HttpPost]
        public async Task<MessageModel<string>> Post([FromBody] sysUserInfo sysUserInfo)
        {
            var data = new MessageModel<string>();

            #region 验证用户名和昵称都不允许重复 [EditBy shaocx,2021-10-12]
            bool isExist = await _sysUserInfoServices.IsExistSameUserName(sysUserInfo.uLoginName, sysUserInfo.uRealName, 0);
            if (isExist)
            {
                return MessageModel<string>.Fail("存在同名的登录名或昵称！");
            }

            #endregion

            sysUserInfo.uLoginPWD = MD5Helper.MD5Encrypt32(sysUserInfo.uLoginPWD);
            sysUserInfo.uRemark = _user.Name;
            sysUserInfo.uCreateTime = DateTime.Now;
            sysUserInfo.uUpdateTime = DateTime.Now;

            var id = await _sysUserInfoServices.Add(sysUserInfo);
            data.success = id > 0;
            if (data.success)
            {
                data.response = id.ObjToString();
                data.msg = "添加成功";
            }

            return data;
        }

        /// <summary>
        /// 更新用户与角色
        /// </summary>
        /// <param name="sysUserInfo"></param>
        /// <returns></returns>
        // PUT: api/User/5
        [HttpPut]
        public async Task<MessageModel<string>> Put([FromBody] sysUserInfo sysUserInfo)
        {
            // 这里使用事务处理

            var data = new MessageModel<string>();
            try
            {


                if (sysUserInfo != null && sysUserInfo.uID > 0)
                {
                    #region 验证用户名和昵称都不允许重复 [EditBy shaocx,2021-10-12]
                    bool isExist = await _sysUserInfoServices.IsExistSameUserName(sysUserInfo.uLoginName, sysUserInfo.uRealName, sysUserInfo.uID);
                    if (isExist)
                    {
                        return MessageModel<string>.Fail("存在同名的登录名或昵称！");
                    }

                    #endregion

                    _unitOfWork.BeginTran();
                    if (sysUserInfo.RIDs.Count > 0)
                    {
                        // 无论 Update Or Add , 先删除当前用户的全部 U_R 关系
                        var usreroles = (await _userRoleServices.Query(d => d.UserId == sysUserInfo.uID)).Select(d => d.Id.ToString()).ToArray();
                        if (usreroles.Count() > 0)
                        {
                            var isAllDeleted = await _userRoleServices.DeleteByIds(usreroles);
                        }

                        // 然后再执行添加操作
                        var userRolsAdd = new List<UserRole>();
                        sysUserInfo.RIDs.ForEach(rid =>
                       {
                           userRolsAdd.Add(new UserRole(sysUserInfo.uID, rid));
                       });

                        await _userRoleServices.Add(userRolsAdd);

                    }

                    sysUserInfo.uUpdateTime = DateTime.Now;
                    data.success = await _sysUserInfoServices.Update(sysUserInfo);

                    _unitOfWork.CommitTran();

                    if (data.success)
                    {
                        data.msg = "更新成功";
                        data.response = sysUserInfo?.uID.ObjToString();
                    }
                }
            }
            catch (Exception e)
            {
                _unitOfWork.RollbackTran();
                _logger.LogError(e, e.Message);
            }

            return data;
        }


        /// <summary>
        /// 更新用户密码等信息
        /// </summary>
        /// <param name="sysUserInfo"></param>
        /// <returns></returns>
        // PUT: api/User/5
        [HttpPut]
        public async Task<MessageModel<string>> UpdatePerson([FromBody] UpdateSysUserInfoParam sysUserInfo)
        {
            // 这里使用事务处理

            var data = new MessageModel<string>();
            try
            {
                _unitOfWork.BeginTran();

                if (sysUserInfo != null && sysUserInfo.uID > 0)
                {
                    var user = await _sysUserInfoServices.QueryById(sysUserInfo.uID);
                    if (sysUserInfo.isUpdatePWD)
                    {
                        user.uLoginPWD = MD5Helper.MD5Encrypt32(sysUserInfo.uLoginPWDNew);
                    }
                    user.uRemark = sysUserInfo.uRemark;
                    user.uRealName = sysUserInfo.uRealName;

                    //判断如果用户切换了头像或者是清空了头像，要把img文件删除
                    if (!string.IsNullOrEmpty(user.tdLogo) && user.tdLogo != sysUserInfo.tdLogo)
                    {
                        //说明用户切换了头像或者是清空了头像
                        var currentTdLogo = user.tdLogo.Substring(1, user.tdLogo.Length - 1);
                        string path = Path.Combine(_environment.WebRootPath, currentTdLogo);
                        //文件是否存在
                        if (System.IO.File.Exists(path))
                        {
                            //删除文件
                            System.IO.File.Delete(path);
                        }
                    }
                    user.tdLogo = sysUserInfo.tdLogo;
                    user.uUpdateTime = DateTime.Now;



                    data.success = await _sysUserInfoServices.Update(user);

                    _unitOfWork.CommitTran();

                    if (data.success)
                    {
                        data.msg = "更新成功";
                        data.response = sysUserInfo?.uID.ObjToString();
                    }
                }
            }
            catch (Exception e)
            {
                _unitOfWork.RollbackTran();
                _logger.LogError(e, e.Message);
            }

            return data;
        }

        /// <summary>
        /// 删除用户
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        // DELETE: api/ApiWithActions/5
        [HttpDelete]
        public async Task<MessageModel<string>> Delete(int id)
        {
            var data = new MessageModel<string>();
            if (id > 0)
            {
                var userDetail = await _sysUserInfoServices.QueryById(id);
                userDetail.tdIsDelete = true;
                data.success = await _sysUserInfoServices.Update(userDetail);
                if (data.success)
                {
                    data.msg = "删除成功";
                    data.response = userDetail?.uID.ObjToString();
                }
            }

            return data;
        }
    }
}
